package InterfaceOffer;

import java.util.Scanner;

// 小美练习吉他
// 一个小时没做出来
public class MtSolution3 {
    public static void main(String[] args) {
        /*
         * dp[i] 表示截止到i时间位置，所能获得的最大收益, x 表示当前的状态值
         * 对于每个小时，小美可以练，也可以不练
         * dp[i] = max(dp[i-1]+x , dp[i-2]+x+b+A , dp[i-3]+x+2*b+A , ... dp[i-M]+x+(M-1)*b+A) , M=1,2,3,...
         * (M-1)*b 代表休息导致的状态增加的补偿
         * A 代表休息导致的状态没减少的补偿
         * */
        Scanner in = new Scanner(System.in);
        int x, a, b, n, t;
        t = in.nextInt();
        for (int o = 0; o < t; o++) {
            x = in.nextInt();
            a = in.nextInt();
            b = in.nextInt();
            n = in.nextInt();
            int dp[] = new int[n + 1];
            int A[] = new int[n + 1]; // A 代表截止到dp对应的时间点，获得最大收益的时候，休息过的次数
            dp[0] = 0;
            for (int i = 1; i < n + 1; i++) {
                int max = Integer.MIN_VALUE;
                int M = 1;
                int minM = 1;
                // 遵循原则，当收益相同时，选择休息次数更多的情况
                while (i - M >= 0) {
                    if (max < dp[i - M] + x + (M - 1) * b + A[i - M] * a) {
                        max = dp[i - M] + x + (M - 1) * b + A[i - M] * a;
                        minM = M; // 记录获得最大收益的时候，是M选择几的情况
                    } else if (max == dp[i - M] + x + (M - 1) * b + A[i - M] * a) {
                        if (A[i - minM] <= A[i - M]) {
                            minM = M;
                            A[i - minM]++;
                        }
                    }
                    M++;
                }
                x -= a;
                dp[i] = max;
                A[i] = A[i - minM];
            }
            System.out.println(dp[n]);
        }
    }
}
